﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Reflection;
using System.IO;
using RemoteTestRunner.Contracts;
using System.Xml.Xsl;
using System.Xml.Linq;

namespace RemoteTestRunner.BusinessLogic
{
    public abstract class TrxParserBase
    {
        #region Private Attributes
        protected const string MultiAssertFileSuffix = ".MultiAssertOutput.xml";
        protected abstract string RootNamespace { get; }
        #endregion

        protected XmlDocument GetTestResultXmlDocument(string testResultsPath, out XmlNamespaceManager nsm)
        {
            var doc = new XmlDocument();
            nsm = new XmlNamespaceManager(doc.NameTable);

            // Create namespace manager for the namespace used by MSTest.exe
            nsm.AddNamespace("ns", RootNamespace);

            // Load the results document
            doc.Load(testResultsPath);
            return doc;
        }

        protected string ApplyXslTransformation(TestResult testResult)
        {
            // Load up the XSL file.
            var settings = new XsltSettings(true, false);
            var xslt = new XslCompiledTransform();
            var resource = GetResource("RemoteTestRunner.BusinessLogic.MultiAssertReport.MultiAssertReport.xsl");

            using (var reader = new StringReader(resource))
            {
                var xmlReader = new XmlTextReader(reader);
                xslt.Load(xmlReader, settings, null);

                // Prepare the output stream.
                using (var stringWriter = new StringWriter())
                {
                    var writer = new XmlTextWriter(stringWriter);

                    // Transform the raw data and return the result.
                    // Create an XML stream that looks like <Files><File>c:\...</File></Files>
                    var externalFiles = new XElement(
                        "Files",
                        from f in testResult.MultiAssertResults
                        select new XElement("File", f.FileName));

                    var doc = new XmlDocument();
                    doc.LoadXml(externalFiles.ToString());
                    XmlNode node = doc;

                    xslt.Transform(node, writer);

                    return stringWriter.ToString();
                }
            }
        }

        protected string GetResource(string resourceName)
        {
            string result = null;

            var assembly = Assembly.GetExecutingAssembly();

            if (assembly != null)
            {
                using (var textReader = new StreamReader(assembly.GetManifestResourceStream(resourceName)))
                {
                    result = textReader.ReadToEnd();
                }
            }

            return result;
        }
    }
}
